<!-- 物料收发明细单 material-detail -->
<template>
  <!-- 搜索栏：支持关键维度筛选 -->
  <ContentWrap class="search-wrap">
    <el-form
      :model="queryParams"
      ref="queryFormRef"
      :inline="true"
      label-width="88px"
      class="query-form"
    >
      <el-form-item label="会计期间" prop="accountPeriod">
        <el-input
          v-model="queryParams.accountPeriod"
          placeholder="请输入会计期间"
          clearable
          @keyup.enter="handleQuery"
          class="!w-240px"
        />
      </el-form-item>
      <el-form-item label="物料长代码" prop="materialLongCode">
        <el-input
          v-model="queryParams.materialLongCode"
          placeholder="请输入物料长代码（如01.002.174）"
          clearable
          @keyup.enter="handleQuery"
          class="!w-240px"
        />
      </el-form-item>
      <el-form-item label="物料名称" prop="materialName">
        <el-input
          v-model="queryParams.materialName"
          placeholder="请输入物料名称（如蓝莓干）"
          clearable
          @keyup.enter="handleQuery"
          class="!w-240px"
        />
      </el-form-item>
      <el-form-item label="部门名称" prop="deptName">
        <el-select
          v-model="queryParams.deptName"
          placeholder="请选择部门"
          clearable
          class="!w-240px"
        >
          <el-option
            v-for="dept in deptList"
            :key="dept.code"
            :label="dept.name"
            :value="dept.name"
          />
        </el-select>
      </el-form-item>
      <el-form-item label="日期范围" prop="dateRange">
        <el-date-picker
          v-model="queryParams.dateRange"
          value-format="YYYY-MM-DD"
          type="daterange"
          start-placeholder="开始日期"
          end-placeholder="结束日期"
          class="!w-240px"
        />
      </el-form-item>
      <el-form-item>
        <el-button @click="handleQuery" type="primary"
          ><Icon icon="ep:search" class="mr-5px" /> 搜索</el-button
        >
        <el-button @click="resetQuery"><Icon icon="ep:refresh" class="mr-5px" /> 重置</el-button>
        <el-button type="success" plain @click="handleExport" :loading="exportLoading">
          <Icon icon="ep:download" class="mr-5px" /> 导出
        </el-button>
      </el-form-item>
    </el-form>
  </ContentWrap>

  <!-- 表格区域：完整字段+指定总计 -->
  <ContentWrap class="table-wrap">
    <el-table
      v-loading="tableLoading"
      :data="inventoryList"
      :stripe="true"
      :show-overflow-tooltip="true"
      row-key="billNo"
      show-summary
      :summary-method="calculateTotal"
      class="inventory-table"
    >
      <!-- 表格列：严格对应需求字段 -->
      <el-table-column label="会计期间" align="center" prop="accountPeriod" min-width="110" />
      <el-table-column label="物料长代码" align="center" prop="materialLongCode" min-width="140" />
      <el-table-column label="物料名称" align="center" prop="materialName" min-width="120" />
      <el-table-column label="规格型号" align="center" prop="specification" min-width="120" />
      <el-table-column label="日期" align="center" prop="date" min-width="120" />
      <el-table-column label="单据号码" align="center" prop="billNo" min-width="140" />
      <el-table-column label="部门编码" align="center" prop="deptCode" min-width="120" />
      <el-table-column label="部门名称" align="center" prop="deptName" min-width="180" />
      <el-table-column label="凭证字号" align="center" prop="voucherNo" min-width="120" />
      <el-table-column label="期初结存单位(基本)" align="center" prop="beginUnit" min-width="150" />
      <el-table-column
        label="期初结存单价(基本)"
        align="right"
        prop="beginUnitPrice"
        min-width="150"
      />
      <el-table-column label="期初结存数量(基本)" align="right" prop="beginQty" min-width="150" />
      <el-table-column label="期初结存金额" align="right" prop="beginAmount" min-width="120" />
      <el-table-column label="收入单价(基本)" align="right" prop="inUnitPrice" min-width="140" />
      <el-table-column label="收入数量(基本)" align="right" prop="inQty" min-width="140" />
      <el-table-column label="收入金额" align="right" prop="inAmount" min-width="120" />
      <el-table-column label="发出单价(基本)" align="right" prop="outUnitPrice" min-width="140" />
      <el-table-column label="发出数量(基本)" align="right" prop="outQty" min-width="140" />
      <el-table-column label="发出金额" align="right" prop="outAmount" min-width="120" />
      <el-table-column label="结存单价(基本)" align="right" prop="endUnitPrice" min-width="140" />
      <el-table-column label="结存数量(基本)" align="right" prop="endQty" min-width="140" />
      <el-table-column label="结存金额" align="right" prop="endAmount" min-width="120" />
    </el-table>

    <!-- 分页 -->
    <div class="pagination-wrap">
      <Pagination
        :total="totalCount"
        v-model:page="queryParams.pageNo"
        v-model:limit="queryParams.pageSize"
        @pagination="getInventoryList"
        layout="total, sizes, prev, pager, next, jumper"
      />
    </div>
  </ContentWrap>
</template>

<script setup lang="ts">
import { ref, reactive, onMounted } from 'vue'
import download from '@/utils/download'

/** 页面配置 */
defineOptions({ name: 'MaterialInventoryDetail' })

const { t } = useI18n()

/** 状态管理 */
const tableLoading = ref(false)
const exportLoading = ref(false)
const queryFormRef = ref()
const inventoryList = ref<InventoryVO[]>([]) // 物料收发存列表
const totalCount = ref(0) // 总条数

/** 搜索参数 */
const queryParams = reactive({
  accountPeriod: undefined, // 会计期间
  materialLongCode: undefined, // 物料长代码
  materialName: undefined, // 物料名称
  deptName: undefined, // 部门名称
  dateRange: [], // 日期范围
  pageNo: 1, // 当前页
  pageSize: 10 // 每页条数
})

/** 基础数据列表（下拉选项） */
const deptList = ref([
  { code: '04.05', name: '配餐部（南航基地新厂房）' },
  { code: '04.01', name: '生产一部（总厂）' },
  { code: '04.02', name: '生产二部（分厂）' },
  { code: '03.01', name: '研发部' },
  { code: '02.03', name: '采购部' }
])
const materialList = ref([
  { longCode: '01.002.174', name: '蓝莓干', spec: '', unit: '袋' },
  { longCode: '01.002.175', name: '葡萄干', spec: '500g/包', unit: '包' },
  { longCode: '01.003.001', name: '核桃仁', spec: '200g/罐', unit: '罐' },
  { longCode: '02.001.012', name: '白砂糖', spec: '10kg/袋', unit: '袋' },
  { longCode: '02.001.013', name: '冰糖', spec: '5kg/袋', unit: '袋' }
])

/** 定义物料收发存数据类型 */
interface InventoryVO {
  accountPeriod: string // 会计期间
  materialLongCode: string // 物料长代码
  materialName: string // 物料名称
  specification: string // 规格型号
  date: string // 日期
  billNo: string // 单据号码
  deptCode: string // 部门编码
  deptName: string // 部门名称
  voucherNo: string // 凭证字号
  beginUnit: string // 期初结存单位(基本)
  beginUnitPrice: number // 期初结存单价(基本)
  beginQty: number // 期初结存数量(基本)
  beginAmount: number // 期初结存金额
  inUnitPrice: number // 收入单价(基本)
  inQty: number // 收入数量(基本)
  inAmount: number // 收入金额
  outUnitPrice: number // 发出单价(基本)
  outQty: number // 发出数量(基本)
  outAmount: number // 发出金额
  endUnitPrice: number // 结存单价(基本)
  endQty: number // 结存数量(基本)
  endAmount: number // 结存金额
}

/** 模拟API接口 */
const InventoryApi = {
  // 获取物料收发存列表
  getInventoryList: async (
    params: typeof queryParams
  ): Promise<{ list: InventoryVO[]; total: number }> => {
    await new Promise((resolve) => setTimeout(resolve, 600)) // 模拟网络延迟

    const mockList: InventoryVO[] = []
    const total = 92 // 模拟总条数
    const start = (params.pageNo - 1) * params.pageSize
    const end = Math.min(start + params.pageSize, total)

    // 生成模拟数据（基于用户样例扩展）
    for (let i = start; i < end; i++) {
      const material = materialList.value[Math.floor(Math.random() * materialList.value.length)]
      const dept = deptList.value[Math.floor(Math.random() * deptList.value.length)]
      const date = new Date()
      date.setDate(date.getDate() - Math.floor(Math.random() * 30)) // 近30天
      const formattedDate = date.toISOString().split('T')[0] // YYYY-MM-DD

      // 基础数值计算（模拟合理的收发存逻辑）
      const beginQty = Math.floor(Math.random() * 200) + 50 // 期初数量50-250
      const beginUnitPrice = parseFloat((Math.random() * 10 + 0.1).toFixed(1)) // 期初单价0.1-10.1
      const beginAmount = parseFloat((beginQty * beginUnitPrice).toFixed(1)) // 期初金额

      const inQty = Math.random() > 0.4 ? Math.floor(Math.random() * 100) + 10 : 0 // 60%概率有收入
      const inUnitPrice =
        inQty > 0 ? parseFloat((Math.random() * 5 + beginUnitPrice).toFixed(1)) : 0
      const inAmount = parseFloat((inQty * inUnitPrice).toFixed(1))

      const outQty = Math.random() > 0.3 ? Math.floor(Math.random() * 80) + 5 : 0 // 70%概率有发出
      const outUnitPrice =
        outQty > 0 ? parseFloat((Math.random() * 3 + beginUnitPrice).toFixed(1)) : 0
      const outAmount = parseFloat((outQty * outUnitPrice).toFixed(1))

      // 结存计算（期初+收入-发出）
      const endQty = beginQty + inQty - outQty
      const endUnitPrice =
        endQty > 0 ? parseFloat(((beginAmount + inAmount - outAmount) / endQty).toFixed(1)) : 0
      const endAmount = parseFloat((endQty * endUnitPrice).toFixed(1))

      mockList.push({
        accountPeriod: '2025.9', // 固定会计期间（可根据需求调整）
        materialLongCode: material.longCode,
        materialName: material.name,
        specification: material.spec,
        date: formattedDate,
        billNo: `SOUT${(130730 + i).toString()}`, // 单据编号递增（匹配样例格式）
        deptCode: dept.code,
        deptName: dept.name,
        voucherNo: Math.random() > 0.6 ? `记-${Math.floor(Math.random() * 1000 + 100)}` : '', // 40%概率有凭证字号
        beginUnit: material.unit,
        beginUnitPrice,
        beginQty,
        beginAmount,
        inUnitPrice,
        inQty,
        inAmount,
        outUnitPrice,
        outQty,
        outAmount,
        endUnitPrice,
        endQty,
        endAmount
      })
    }

    // 模拟筛选逻辑（实际项目由后端处理）
    const filteredList = mockList.filter((item) => {
      if (params.accountPeriod && !item.accountPeriod.includes(params.accountPeriod)) return false
      if (params.materialLongCode && !item.materialLongCode.includes(params.materialLongCode))
        return false
      if (params.materialName && !item.materialName.includes(params.materialName)) return false
      if (params.deptName && item.deptName !== params.deptName) return false
      if (params.dateRange.length) {
        const startDate = new Date(params.dateRange[0])
        const endDate = new Date(params.dateRange[1])
        const itemDate = new Date(item.date)
        if (itemDate < startDate || itemDate > endDate) return false
      }
      return true
    })

    return { list: filteredList, total: filteredList.length }
  },

  // 导出物料收发存数据
  exportInventoryList: async (params: typeof queryParams): Promise<Blob> => {
    await new Promise((resolve) => setTimeout(resolve, 1000)) // 模拟导出耗时

    // 获取所有筛选数据（不分页）
    const { list } = await InventoryApi.getInventoryList({ ...params, pageNo: 1, pageSize: 9999 })

    // 构建CSV表头与内容（严格对应表格字段）
    const header =
      '会计期间,物料长代码,物料名称,规格型号,日期,单据号码,部门编码,部门名称,凭证字号,期初结存单位(基本),期初结存单价(基本),期初结存数量(基本),期初结存金额,收入单价(基本),收入数量(基本),收入金额,发出单价(基本),发出数量(基本),发出金额,结存单价(基本),结存数量(基本),结存金额\n'
    let content = header
    list.forEach((item) => {
      content += `${item.accountPeriod},${item.materialLongCode},${item.materialName},${
        item.specification || ''
      },${item.date},${item.billNo},${item.deptCode},${item.deptName},${item.voucherNo || ''},${
        item.beginUnit
      },${item.beginUnitPrice},${item.beginQty},${item.beginAmount},${item.inUnitPrice},${
        item.inQty
      },${item.inAmount},${item.outUnitPrice},${item.outQty},${item.outAmount},${
        item.endUnitPrice
      },${item.endQty},${item.endAmount}\n`
    })

    return new Blob([content], { type: 'text/csv;charset=utf-8;' })
  }
}

/** 核心：计算指定8个字段的总计 */
const calculateTotal = ({ columns, data }: { columns: any[]; data: InventoryVO[] }) => {
  const summary: any[] = []
  columns.forEach((column, index) => {
    // 第一列显示"总计"
    if (index === 0) {
      summary[index] = '总计'
      return
    }

    // 1. 期初结存数量(基本)
    if (column.property === 'beginQty') {
      summary[index] = data.reduce((sum, item) => sum + item.beginQty, 0)
      return
    }

    // 2. 期初结存金额
    if (column.property === 'beginAmount') {
      const total = data.reduce((sum, item) => sum + item.beginAmount, 0)
      summary[index] = total.toFixed(1)
      return
    }

    // 3. 收入数量(基本)
    if (column.property === 'inQty') {
      summary[index] = data.reduce((sum, item) => sum + item.inQty, 0)
      return
    }

    // 4. 收入金额
    if (column.property === 'inAmount') {
      const total = data.reduce((sum, item) => sum + item.inAmount, 0)
      summary[index] = total.toFixed(1)
      return
    }

    // 5. 发出数量(基本)
    if (column.property === 'outQty') {
      summary[index] = data.reduce((sum, item) => sum + item.outQty, 0)
      return
    }

    // 6. 发出金额
    if (column.property === 'outAmount') {
      const total = data.reduce((sum, item) => sum + item.outAmount, 0)
      summary[index] = total.toFixed(1)
      return
    }

    // 7. 结存数量(基本)
    if (column.property === 'endQty') {
      summary[index] = data.reduce((sum, item) => sum + item.endQty, 0)
      return
    }

    // 8. 结存金额
    if (column.property === 'endAmount') {
      const total = data.reduce((sum, item) => sum + item.endAmount, 0)
      summary[index] = total.toFixed(1)
      return
    }

    // 其他字段（如单价、单位）不合计，留空
    summary[index] = ''
  })
  return summary
}

/** 获取物料收发存列表 */
const getInventoryList = async () => {
  tableLoading.value = true
  try {
    const { list, total } = await InventoryApi.getInventoryList(queryParams)
    inventoryList.value = list
    totalCount.value = total
  } catch (error) {
    console.error('获取物料收发存列表失败:', error)
    message.info('数据加载失败，请重试')
  } finally {
    tableLoading.value = false
  }
}

/** 搜索操作 */
const handleQuery = () => {
  queryParams.pageNo = 1
  getInventoryList()
}

/** 重置操作 */
const resetQuery = () => {
  if (queryFormRef.value) {
    queryFormRef.value.resetFields()
  }
  Object.assign(queryParams, {
    accountPeriod: undefined,
    materialLongCode: undefined,
    materialName: undefined,
    deptName: undefined,
    dateRange: [],
    pageNo: 1
  })
  getInventoryList()
}

/** 导出操作 */
const handleExport = async () => {
  try {
    await message.exportConfirm()
    exportLoading.value = true
    const blob = await InventoryApi.exportInventoryList(queryParams)
    const exportDate = new Date().toLocaleDateString()
    download.excel(blob, `物料收发存明细表_${exportDate}.xls`)
    message.success('导出成功')
  } catch (error) {
    if (error !== 'cancel') {
      // 排除用户取消
      console.error('导出失败:', error)
      message.info('导出失败，请重试')
    }
  } finally {
    exportLoading.value = false
  }
}

/** 页面初始化 */
onMounted(() => {
  getInventoryList()
})

/** 模拟权限指令 */
const vHasPermi = {
  mounted(el: HTMLElement, binding: any) {
    const hasPermi = true // 实际项目需按权限判断
    if (!hasPermi) el.style.display = 'none'
  }
}
</script>

<style scoped lang="scss">
.material-inventory-page {
  padding: 16px;
  background-color: #f9fafb;

  .page-header {
    margin-bottom: 20px;
    h2 {
      font-size: 18px;
      font-weight: 600;
      color: #1f2937;
    }
  }

  .search-wrap {
    margin-bottom: 16px;
    .query-form {
      padding: 16px;
      background: #fff;
      border-radius: 8px;
      box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05);
    }
  }

  .table-wrap {
    .inventory-table {
      background: #fff;
      border-radius: 8px;
      overflow: hidden;
      // 总计行样式（突出显示）
      .el-table__footer-wrapper {
        .el-table__row {
          background-color: #f0f7ff;
          font-weight: 700;
          color: #165dff;
        }
      }
      // 数值列右对齐（确保总计与数据对齐）
      .el-table-column--align-right {
        .cell {
          text-align: right !important;
        }
      }
    }

    .pagination-wrap {
      margin-top: 16px;
      text-align: right;
    }
  }
}
</style>